from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.response import Response
from user.models import *
from goods.models import *
from .ser import *
import redis


class GetCarousel(APIView):
    def get(self, request):
        car_data = Carousel.objects.all()
        ser = CarouselSer(car_data, many=True)
        return Response({
            'code': 200,
            'msg': '加载轮播图成功',
            'carousel': ser.data
        })


class OneCategory(APIView):
    # 获取一类商品信息
    def get(self, request):
        # 获取种类信息
        cate_name = request.query_params.get('categoryName')
        # ORM获取种类信息
        try:
            cate_data = Category.objects.get(cate_name=cate_name)
        except Exception as e:
            print(e)
            return Response({
                'msg': '此类商品类别不存在',
                'code': 204
            })
        # 根据类别获取商品信息
        goods_data = cate_data.goods_set.all()
        # 序列号商品信息
        ser = GoodSer(goods_data, many=True)
        return Response({
            'msg': '成功获取商品信息',
            'code': 200,
            'result': ser.data
        })


class HotProduct(APIView):
    def get(self, request):
        # 获取种类信息，热门商品是个列表
        cate_list = request.query_params.getlist('categoryName[]')
        # 根据类别名获取种类信息
        cate_data_list = []
        for i in cate_list:
            cate_data = Category.objects.get(cate_name=i)
            cate_data_list.append(cate_data)
        # 根据类别获取商品信息
        goods_data_list = []
        for i in cate_data_list:
            goods_data_list.append(i.goods_set.all())
        # 将商品信息合并
        from functools import reduce
        goods_data_queryset = reduce((lambda x, y: x | y), goods_data_list).order_by('-count')
        # 序列号
        ser = GoodSer(goods_data_queryset, many=True)
        return Response({
            'msg': '成功获取商品信息',
            'code': 200,
            'result': ser.data
        })


class OneGood(APIView):
    def get(self, request):
        # 获取商品id
        good_id = request.query_params.get('productID')
        try:
            good_data = Goods.objects.get(id=good_id)
        except Exception as e:
            print(e)
            return Response({
                'msg': '商品不存在',
                'code': 204
            })
        ser = GoodSer(good_data)
        return Response(ser.data)


class OneGoodImg(APIView):
    def get(self, request):
        # 获取商品id
        good_id = request.query_params.get('productID')
        try:
            good_data = Goods.objects.get(id=good_id)
        except Exception as e:
            print(e)
            return Response({
                'msg': '图片存在',
                'code': 204
            })
        img_data = good_data.goodimg_set.all()
        ser = GoodimgSer(img_data, many=True)
        return Response(ser.data)


class History(APIView):
    def post(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
            print(user_info)
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户不存在或未登录',
                'code': 204
            })
        good_id = request.data.get('productID')
        try:
            good_data = Goods.objects.get(id=good_id)
        except Exception as e:
            print(e)
            return Response({
                'msg': '商品不存在',
                'code': 204
            })
        # 添加历史记录
        history_key = 'history_%s' % user.username
        res = redis.Redis(host='localhost', port=6379, db=0)
        res.lrem(history_key, 0, good_id)
        res.lpush(history_key, good_id)
        res.ltrim(history_key, 0, 4)
        return Response({
            'code': 200,
            'msg': '成功',
        })


class Collection(APIView):
    def get(self, request):
        try:
            user = User.objects.get(id = request.user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'code': 204,
                'msg': '用户不存在或未登录'
            })
        collect_data = GoodsCollect.objects.filter(user=user)
        if collect_data.count() == 0:
            return Response({
            'code': 204,
            'msg': '用户没有任何收藏',
        })
        collect_list = []
        for i in collect_data:
            collect_list.append({
                'id': i.goods.id,
                'sku_name': i.goods.sku_name,
                'title': i.goods.title,
                'price': i.goods.price,
                'selling_price': i.goods.selling_price,
                'img': i.goods.img
            })
        return Response({
            'code': 200,
            'collect_list': collect_list
        })


    def post(self, request):
        # 判断用户是否登录
        try:
            user = User.objects.get(id=request.user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户不存在或未登录',
                'code': 204
            })
        # 判断收藏是否存在
        good_id = request.data.get('productID')
        collect_data = GoodsCollect.objects.filter(user=user, goods_id=good_id)
        if collect_data.count() > 0:
            return Response({
                'msg': '收藏已存在',
                'code': 204
            })
        # 收藏不存在，添加收藏
        try:
            GoodsCollect.objects.create(
                user=user,
                goods_id=good_id
            )
        except Exception as e:
            print(e)
            return Response({
                'msg': '添加收藏失败',
                'code': 204
            })
        return Response({
            'msg': '收藏成功',
            'code': 200
        })

    def delete(self, request):
        try:
            user = User.objects.get(id=request.user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户不存在或未登录',
                'code': 204
            })
        good_id = request.data.get('productID')
        try:
            GoodsCollect.objects.get(user=user, goods_id=good_id).delete()
        except Exception as e:
            print(e)
            return Response({
                'msg': '删除收藏失败',
                'code': 204
            })
        return Response({
            'msg': '删除收藏成功',
            'code': 200
        })


class UserCart(APIView):
    def get(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        # 拼接购物车的键
        cart_key = 'cart_%s' % user.username
        # 添加购物车时商品自动勾选
        cart_selected_key = 'cart_selected_%s' % user.username
        # 获取数据
        res = redis.Redis(host='localhost', port=6379, db=1)
        cart_list = res.hgetall(cart_key)
        select_list = res.smembers(cart_selected_key)
        select_list2 = [i.decode() for i in select_list]
        result_data = []
        # key 商品id， value 商品数量
        for key, value in cart_list.items():
            good_id = key.decode()
            good_data = Goods.objects.get(id=good_id)
            result_data.append({
                'id': cart_key,
                'productID': good_data.id,
                'productName': good_data.sku_name,
                'productImg': good_data.img,
                'price': good_data.price,
                'num': value.decode(),
                'maxNum': good_data.stock,
                'check': good_id in select_list2,
            })

        return Response({
            'msg': '查询购物车成功',
            'code': 200,
            'shoppingCartData':result_data
        })

    def post(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        # 获取商品信息
        good_id = request.data.get('productID')
        good_data = Goods.objects.get(id=good_id)
        # 拼接购物车的键
        cart_key = 'cart_%s' % user.username
        # 添加购物车时商品自动勾选
        cart_selected_key = 'cart_selected_%s' % user.username
        # 判断库存
        if good_data.stock <= 0:
            return Response({
                'msg': '库存不足, 无法购买',
                'code': 203
            })
        # 判断购物车是否有该商品
        res = redis.Redis(host='localhost', port=6379, db=1)
        # 获取商品在购物车的数量
        num = res.hget(cart_key, good_id)
        if num:  # 购物车存在该商品
            num = int(num.decode()) + 1
            if num > good_data.stock:
                res.close()
                return Response({
                    'msg': '加购数量达到上限，无法购买',
                    'code': 202
                })
            res.hset(cart_key, good_id, str(num))  # 购物车数量+1
            res.sadd(cart_selected_key, good_id)  # 选中商品
            return Response({
                'msg': '购物车存在该商品，数量+1',
                'code': 201
            })
        else:  # 购物车不存在该商品
            res.hset(cart_key, good_id, 1)  # 添加商品到购物车
            res.sadd(cart_selected_key, good_id)  # 选中商品
            res.close()
            return Response({
                'code': 200,
                'msg': '加入购物车成功',
                'shoppingCartData': {
                    'id': cart_key,  # 购物车名字
                    'productID': good_id,  # 商品id
                    'productName': good_data.sku_name,  # 商品名
                    'productImg': good_data.img,
                    'price': good_data.price,
                    'num': 1,
                    'maxNum': good_data.stock,
                    'check': True
                }
            })

    def put(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        # 获取商品信息
        good_id = request.data.get('productID')
        num = request.data.get('num')
        cart_key = 'cart_%s' % user.username
        # 修改数据库的数据
        try:
            res = redis.Redis(host='localhost', port=6379, db=1)
            res.hset(cart_key, good_id, num)
            res.close()
            return Response({
                'msg': '数量修改成功',
                'code': 200
            })
        except Exception as e:
            print(e)
            return Response({
                'msg': '数量修改失败',
                'code': 204
            })
    def delete(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        # 获取商品信息
        good_id = request.data.get('productID')
        cart_key = 'cart_%s' % user.username
        cart_selected_key = 'cart_selected_%s' % user.username
        # 删除商品对应的商品信息
        # 连接redis数据库， 修改数据
        res = redis.Redis(host='localhost', port=6379, db=1)
        res.hdel(cart_key, good_id)
        res.srem(cart_selected_key, good_id)
        res.close()
        return Response({
            'msg': '删除成功',
            'code': 200
        })


class Selection(APIView):
    def put(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        # 获取商品信息
        good_id = request.data.get('productID')
        select_flag = request.data.get('val')
        cart_selected_key = 'cart_selected_%s' % user.username
        # 连接redis数据库， 修改数据
        res = redis.Redis(host='localhost', port=6379, db=1)
        if select_flag:
            res.sadd(cart_selected_key, good_id)
            res.close()
            return Response({
                'msg': '选中成功',
                'code': 200
            })
        else:
            res.srem(cart_selected_key, good_id)
            res.close()
            return Response({
                'msg': '取消选中成功',
                'code': 200
            })

    def post(self, request):
        # 判断用户是否登录
        try:
            user_info = request.user_info
            user = User.objects.get(id=user_info.get('user_id'))
        except Exception as e:
            print(e)
            return Response({
                'msg': '用户未登录',
                'code': 204
            })
        all_flag = request.data.get('val')
        cart_key = 'cart_%s' % user.username
        cart_selected_key = 'cart_selected_%s' % user.username
        # 连接redis数据库， 修改数据
        res = redis.Redis(host='localhost', port=6379, db=1)
        if all_flag:
            # 获取购物车中的所有商品id
            good_id_list = res.hkeys(cart_key)
            # 往选中框添加选中商品
            for i in good_id_list:
                res.sadd(cart_selected_key, i.decode())
            res.close()
            return Response({
                'msg': '全选成功',
                'code': 200
            })
        else:
            # 删除全部选中的商品
            res.delete(cart_selected_key)
            res.close()
            return Response({
                'msg': '取消全选成功',
                'code': 200
            })













